import { _decorator, Component } from 'cc';
import { BasePositionConfigs, BuildingConfig, isResourceTildeType, MapSettings, UnitConfig } from './battle/Const';
import { BuildingType, CommandType, DirectionType, EntityType, TildeType, UnitType } from './battle/Enums';
import { BuildingModel, CommandParam, CommandParamMap, UnitModel } from './battle/Model';
import { GameConfig } from './config';
import { GameCore } from './core/game';
import { MapManager, MapTile } from './view/map/MapManager';
import { PlayerManager } from './view/player/PlayerManager';
import { BattleScene } from './view/scene/BattleScene';
import { battleScene } from './view/scene/BattleSceneManager';
import { LOG } from './ConsoleLogCtrl';

// 确保可以访问全局 gc 对象
declare const gc: GameCore;

const { ccclass } = _decorator;

/**
 * 战斗测试脚本
 * 用于测试战斗场景的表现
 */
@ccclass('TestBattleScript')
export class TestBattleScript extends Component {
    // 类常量定义
    private static readonly BASE_SURROUNDING_DISTANCE: number = 10; // 单元基地周边格子距离
    private static readonly SOLDIERS_PER_PLAYER: number = 2; // 每个玩家生成的士兵数量
    private static readonly DOCTORS_PER_PLAYER: number = 2; // 每个玩家生成的治疗兵数量
    private static readonly ARCHERS_PER_PLAYER: number = 2; // 每个玩家生成的弓箭手数量
    private static readonly WORKERS_PER_PLAYER: number = 2; // 每个玩家生成的建造兵数量
    private static readonly COLLECTORS_PER_PLAYER: number = 2; // 每个玩家生成的采集兵数量
    private static readonly BATTLE_ROUNDS: number = 50; // 战斗循环轮次数

    private _battleSceneInstance: BattleScene = null;

    private _playerManager: PlayerManager = null;
    private _mapManager: MapManager = null;

    // 命令日志数组
    private _commandLogs: any[] = [];

    // 当前轮次计数器
    private _currentRound: number = 0;

    // 全局占用位置集合，用于跟踪所有已占用的位置
    private _globalOccupiedPositions: Set<string> = new Set<string>();

    // 记录已经建造过防御塔的建造兵ID
    private workersWhoBuiltTower: Set<number> = new Set<number>();
    // 记录已经建造过城墙的建造兵ID
    private workersWhoBuiltWall: Set<number> = new Set<number>();

    // 命令缓存，使用Map结构为每个玩家分别收集一个完整回合的命令
    private _playerCommandCache: Map<string, CommandParam<keyof CommandParamMap>[]> = new Map();

    onDestroy() {
        LOG.log('TestBattle 脚本销毁');
    }

    /**
     * 开始战斗脚本测试
     */
    public onTestBattleScriptStart() {
        LOG.log('战斗场景加载完成，开始初始化...');

        // 获取战斗场景实例
        this._battleSceneInstance = battleScene.getBattleScene();
        if (!this._battleSceneInstance) {
            LOG.error('获取战斗场景实例失败');
            return;
        }

        // 获取玩家管理器实例
        this._playerManager = new PlayerManager();
        this._playerManager.reset();

        // 创建地图管理器实例
        this._mapManager = new MapManager();
        this._mapManager.reset();

        // 设置玩家管理器和地图管理器的关联
        this._playerManager.setMapManager(this._mapManager);

        // 清空命令日志数组
        this._commandLogs = [];

        // 清空全局占用位置集合
        this._globalOccupiedPositions.clear();

        // 清空已建造防御塔的工人ID集合
        this.workersWhoBuiltTower.clear();

        LOG.log('成功获取战斗场景实例，开始初始化地图...');

        // 步骤1：初始化战斗（创建玩家并初始化地图且创建基地）
        const [player1Id, player2Id] = this.initBattle();

        // 步骤2：按回合顺序执行后续步骤
        this.executeNextPhase(player1Id, player2Id, 'workers');
    }

    /**
     * 步骤1：初始化战斗（创建玩家并初始化地图且创建基地）
     * @returns 返回两个玩家的ID
     */
    private initBattle(): [string, string] {
        LOG.log('初始化战斗...');

        // 重置回合计数器
        this._currentRound = 0;

        // 创建两个玩家
        const player1Id = '祝云龙';
        const player2Id = '曹佳灿';

        // 创建初始化地图（包含构建基地）
        this.executeCommand(this.createInitCommand(player1Id, player2Id));

        // 将基地位置添加到全局占用位置集合
        this._globalOccupiedPositions.add(`${BasePositionConfigs['main3'][0].x},${BasePositionConfigs['main3'][0].y}`);
        this._globalOccupiedPositions.add(`${BasePositionConfigs['main3'][1].x},${BasePositionConfigs['main3'][1].y}`);

        return [player1Id, player2Id];
    }

    /**
     * 步骤2：按回合顺序执行后续阶段
     * @param player1Id 玩家1 ID
     * @param player2Id 玩家2 ID
     * @param phase 当前阶段
     */
    private executeNextPhase(player1Id: string, player2Id: string, phase: string) {
        switch (phase) {
            case 'workers':
                LOG.log('开始生成建造兵阶段...');
                this.generateWorkers(player1Id, player2Id, () => {
                    this.executeNextPhase(player1Id, player2Id, 'collectors');
                });
                break;
            case 'collectors':
                LOG.log('开始生成采集兵阶段...');
                this.generateCollectors(player1Id, player2Id, () => {
                    this.executeNextPhase(player1Id, player2Id, 'soldiers');
                });
                break;
            case 'soldiers':
                LOG.log('开始生成士兵阶段...');
                this.generateSoldiers(player1Id, player2Id, () => {
                    this.executeNextPhase(player1Id, player2Id, 'doctors');
                });
                break;
            case 'doctors':
                LOG.log('开始生成治疗兵阶段...');
                this.generateDoctors(player1Id, player2Id, () => {
                    this.executeNextPhase(player1Id, player2Id, 'archers');
                });
                break;
            case 'archers':
                LOG.log('开始生成弓箭手阶段...');
                this.generateArchers(player1Id, player2Id, () => {
                    this.executeNextPhase(player1Id, player2Id, 'battle');
                });
                break;
            case 'battle':
                LOG.log('开始战斗循环阶段...');
                this.startBattleLoop(player1Id, player2Id, TestBattleScript.BATTLE_ROUNDS);
                break;
        }
    }

    /**
     * 步骤2.1：两个玩家交替在基地周边格子距离内随机生成建造兵单位
     * 基地周边距离：BASE_SURROUNDING_DISTANCE
     * 每个玩家生成的建造兵数量：WORKERS_PER_PLAYER
     */
    private generateWorkers(player1Id: string, player2Id: string, callback?: () => void) {
        LOG.log('开始生成建造兵单位...');

        // 获取玩家基地位置
        const player1Base = { position: BasePositionConfigs['main3'][0] };
        const player2Base = { position: BasePositionConfigs['main3'][1] };

        // 创建玩家1的命令序列
        const player1Commands: CommandParam<keyof CommandParamMap>[] = [];

        // 创建玩家2的命令序列
        const player2Commands: CommandParam<keyof CommandParamMap>[] = [];

        // 为每个玩家生成建造兵
        let player1WorkerCount = 0;
        let player2WorkerCount = 0;

        for (let i = 0; i < TestBattleScript.WORKERS_PER_PLAYER; i++) {
            // 为玩家1准备建造兵位置
            const worker1Pos = this.getRandomPositionAroundBase(
                player1Base.position,
                TestBattleScript.BASE_SURROUNDING_DISTANCE,
                this._globalOccupiedPositions
            );
            if (worker1Pos) {
                // 获取下一个可用的单位ID
                const unitId = this._playerManager.getNextUnitId();
                player1Commands.push(this.createSwapUnitCommand(player1Id, unitId, UnitType.worker, worker1Pos));
                // 标记位置为已占用
                this._globalOccupiedPositions.add(`${worker1Pos.x},${worker1Pos.y}`);
                player1WorkerCount++;
            } else {
                LOG.warn(`玩家1无法在第${i + 1}次尝试中找到有效位置生成建造兵`);
            }

            // 为玩家2准备建造兵位置
            const worker2Pos = this.getRandomPositionAroundBase(
                player2Base.position,
                TestBattleScript.BASE_SURROUNDING_DISTANCE,
                this._globalOccupiedPositions
            );
            if (worker2Pos) {
                // 获取下一个可用的单位ID
                const unitId = this._playerManager.getNextUnitId();
                player2Commands.push(this.createSwapUnitCommand(player2Id, unitId, UnitType.worker, worker2Pos));
                // 标记位置为已占用
                this._globalOccupiedPositions.add(`${worker2Pos.x},${worker2Pos.y}`);
                player2WorkerCount++;
            } else {
                LOG.warn(`玩家2无法在第${i + 1}次尝试中找到有效位置生成建造兵`);
            }
        }

        LOG.log(
            `建造兵生成完成 - 玩家1: ${player1WorkerCount}/${TestBattleScript.WORKERS_PER_PLAYER}, 玩家2: ${player2WorkerCount}/${TestBattleScript.WORKERS_PER_PLAYER}`
        );

        // 按回合执行命令序列
        this.executeCommandsByTurn(player1Commands, player2Commands, () => {
            LOG.log('建造兵生成完成');
            if (callback) callback();
        });
    }

    /**
     * 步骤2.2：两个玩家交替在基地周边格子距离内随机生成士兵单位
     * 基地周边距离：BASE_SURROUNDING_DISTANCE
     * 每个玩家生成的士兵数量：SOLDIERS_PER_PLAYER
     */
    private generateSoldiers(player1Id: string, player2Id: string, callback?: () => void) {
        LOG.log('开始生成士兵单位...');

        // 获取玩家基地位置
        const player1Base = { position: BasePositionConfigs['main3'][0] };
        const player2Base = { position: BasePositionConfigs['main3'][1] };

        // 创建玩家1的命令序列
        const player1Commands: CommandParam<keyof CommandParamMap>[] = [];

        // 创建玩家2的命令序列
        const player2Commands: CommandParam<keyof CommandParamMap>[] = [];

        // 为每个玩家生成士兵
        let player1SoldierCount = 0;
        let player2SoldierCount = 0;

        for (let i = 0; i < TestBattleScript.SOLDIERS_PER_PLAYER; i++) {
            // 为玩家1准备士兵位置
            const soldier1Pos = this.getRandomPositionAroundBase(
                player1Base.position,
                TestBattleScript.BASE_SURROUNDING_DISTANCE,
                this._globalOccupiedPositions
            );
            if (soldier1Pos) {
                // 获取下一个可用的单位ID
                const unitId = this._playerManager.getNextUnitId();
                player1Commands.push(this.createSwapUnitCommand(player1Id, unitId, UnitType.soldier, soldier1Pos));
                // 标记位置为已占用
                this._globalOccupiedPositions.add(`${soldier1Pos.x},${soldier1Pos.y}`);
                player1SoldierCount++;
            } else {
                LOG.warn(`玩家1无法在第${i + 1}次尝试中找到有效位置生成士兵`);
            }

            // 为玩家2准备士兵位置
            const soldier2Pos = this.getRandomPositionAroundBase(
                player2Base.position,
                TestBattleScript.BASE_SURROUNDING_DISTANCE,
                this._globalOccupiedPositions
            );
            if (soldier2Pos) {
                // 获取下一个可用的单位ID
                const unitId = this._playerManager.getNextUnitId();
                player2Commands.push(this.createSwapUnitCommand(player2Id, unitId, UnitType.soldier, soldier2Pos));
                // 标记位置为已占用
                this._globalOccupiedPositions.add(`${soldier2Pos.x},${soldier2Pos.y}`);
                player2SoldierCount++;
            } else {
                LOG.warn(`玩家2无法在第${i + 1}次尝试中找到有效位置生成士兵`);
            }
        }

        LOG.log(
            `士兵生成完成 - 玩家1: ${player1SoldierCount}/${TestBattleScript.SOLDIERS_PER_PLAYER}, 玩家2: ${player2SoldierCount}/${TestBattleScript.SOLDIERS_PER_PLAYER}`
        );

        // 按回合执行命令序列
        this.executeCommandsByTurn(player1Commands, player2Commands, () => {
            LOG.log('士兵生成完成');
            if (callback) callback();
        });
    }

    /**
     * 步骤2.3：两个玩家交替在基地周边格子距离内随机生成治疗兵单位
     * 基地周边距离：BASE_SURROUNDING_DISTANCE
     * 每个玩家生成的治疗兵数量：DOCTORS_PER_PLAYER
     */
    private generateDoctors(player1Id: string, player2Id: string, callback?: () => void) {
        LOG.log('开始生成治疗兵单位...');

        // 获取玩家基地位置
        const player1Base = { position: BasePositionConfigs['main3'][0] };
        const player2Base = { position: BasePositionConfigs['main3'][1] };

        // 创建玩家1的命令序列
        const player1Commands: CommandParam<keyof CommandParamMap>[] = [];

        // 创建玩家2的命令序列
        const player2Commands: CommandParam<keyof CommandParamMap>[] = [];

        // 为每个玩家生成治疗兵
        let player1DoctorCount = 0;
        let player2DoctorCount = 0;

        for (let i = 0; i < TestBattleScript.DOCTORS_PER_PLAYER; i++) {
            // 为玩家1准备治疗兵位置
            const doctor1Pos = this.getRandomPositionAroundBase(
                player1Base.position,
                TestBattleScript.BASE_SURROUNDING_DISTANCE,
                this._globalOccupiedPositions
            );
            if (doctor1Pos) {
                // 获取下一个可用的单位ID
                const unitId = this._playerManager.getNextUnitId();
                player1Commands.push(this.createSwapUnitCommand(player1Id, unitId, UnitType.doctor, doctor1Pos));
                // 标记位置为已占用
                this._globalOccupiedPositions.add(`${doctor1Pos.x},${doctor1Pos.y}`);
                player1DoctorCount++;
            } else {
                LOG.warn(`玩家1无法在第${i + 1}次尝试中找到有效位置生成治疗兵`);
            }

            // 为玩家2准备治疗兵位置
            const doctor2Pos = this.getRandomPositionAroundBase(
                player2Base.position,
                TestBattleScript.BASE_SURROUNDING_DISTANCE,
                this._globalOccupiedPositions
            );
            if (doctor2Pos) {
                // 获取下一个可用的单位ID
                const unitId = this._playerManager.getNextUnitId();
                player2Commands.push(this.createSwapUnitCommand(player2Id, unitId, UnitType.doctor, doctor2Pos));
                // 标记位置为已占用
                this._globalOccupiedPositions.add(`${doctor2Pos.x},${doctor2Pos.y}`);
                player2DoctorCount++;
            } else {
                LOG.warn(`玩家2无法在第${i + 1}次尝试中找到有效位置生成治疗兵`);
            }
        }

        LOG.log(
            `治疗兵生成完成 - 玩家1: ${player1DoctorCount}/${TestBattleScript.DOCTORS_PER_PLAYER}, 玩家2: ${player2DoctorCount}/${TestBattleScript.DOCTORS_PER_PLAYER}`
        );

        // 按回合执行命令序列
        this.executeCommandsByTurn(player1Commands, player2Commands, () => {
            LOG.log('治疗兵生成完成');
            if (callback) callback();
        });
    }

    /**
     * 步骤2.3.5：两个玩家交替在基地周边格子距离内随机生成采集兵单位
     * 基地周边距离：BASE_SURROUNDING_DISTANCE
     * 每个玩家生成的采集兵数量：COLLECTORS_PER_PLAYER
     */
    private generateCollectors(player1Id: string, player2Id: string, callback?: () => void) {
        LOG.log('开始生成采集兵单位...');

        // 获取玩家基地位置
        const player1Base = { position: BasePositionConfigs['main3'][0] };
        const player2Base = { position: BasePositionConfigs['main3'][1] };

        // 创建玩家1的命令序列
        const player1Commands: CommandParam<keyof CommandParamMap>[] = [];

        // 创建玩家2的命令序列
        const player2Commands: CommandParam<keyof CommandParamMap>[] = [];

        // 为每个玩家生成采集兵
        let player1CollectorCount = 0;
        let player2CollectorCount = 0;

        for (let i = 0; i < TestBattleScript.COLLECTORS_PER_PLAYER; i++) {
            // 为玩家1准备采集兵位置
            const collector1Pos = this.getRandomPositionAroundBase(
                player1Base.position,
                TestBattleScript.BASE_SURROUNDING_DISTANCE,
                this._globalOccupiedPositions
            );
            if (collector1Pos) {
                // 获取下一个可用的单位ID
                const unitId = this._playerManager.getNextUnitId();
                player1Commands.push(this.createSwapUnitCommand(player1Id, unitId, UnitType.collect, collector1Pos));
                // 标记位置为已占用
                this._globalOccupiedPositions.add(`${collector1Pos.x},${collector1Pos.y}`);
                player1CollectorCount++;
            } else {
                LOG.warn(`玩家1无法在第${i + 1}次尝试中找到有效位置生成采集兵`);
            }

            // 为玩家2准备采集兵位置
            const collector2Pos = this.getRandomPositionAroundBase(
                player2Base.position,
                TestBattleScript.BASE_SURROUNDING_DISTANCE,
                this._globalOccupiedPositions
            );
            if (collector2Pos) {
                // 获取下一个可用的单位ID
                const unitId = this._playerManager.getNextUnitId();
                player2Commands.push(this.createSwapUnitCommand(player2Id, unitId, UnitType.collect, collector2Pos));
                // 标记位置为已占用
                this._globalOccupiedPositions.add(`${collector2Pos.x},${collector2Pos.y}`);
                player2CollectorCount++;
            } else {
                LOG.warn(`玩家2无法在第${i + 1}次尝试中找到有效位置生成采集兵`);
            }
        }

        LOG.log(
            `采集兵生成完成 - 玩家1: ${player1CollectorCount}/${TestBattleScript.COLLECTORS_PER_PLAYER}, 玩家2: ${player2CollectorCount}/${TestBattleScript.COLLECTORS_PER_PLAYER}`
        );

        // 按回合执行命令序列
        this.executeCommandsByTurn(player1Commands, player2Commands, () => {
            LOG.log('采集兵生成完成');
            if (callback) callback();
        });
    }

    /**
     * 步骤2.4：两个玩家交替在基地周边格子距离内随机生成弓箭手单位
     * 基地周边距离：BASE_SURROUNDING_DISTANCE
     * 每个玩家生成的弓箭手数量：ARCHERS_PER_PLAYER
     */
    private generateArchers(player1Id: string, player2Id: string, callback?: () => void) {
        LOG.log('开始生成弓箭手单位...');

        // 获取玩家基地位置
        const player1Base = { position: BasePositionConfigs['main3'][0] };
        const player2Base = { position: BasePositionConfigs['main3'][1] };

        // 创建玩家1的命令序列
        const player1Commands: CommandParam<keyof CommandParamMap>[] = [];

        // 创建玩家2的命令序列
        const player2Commands: CommandParam<keyof CommandParamMap>[] = [];

        // 为每个玩家生成弓箭手
        let player1ArcherCount = 0;
        let player2ArcherCount = 0;

        for (let i = 0; i < TestBattleScript.ARCHERS_PER_PLAYER; i++) {
            // 为玩家1准备弓箭手位置
            const archer1Pos = this.getRandomPositionAroundBase(
                player1Base.position,
                TestBattleScript.BASE_SURROUNDING_DISTANCE,
                this._globalOccupiedPositions
            );
            if (archer1Pos) {
                // 获取下一个可用的单位ID
                const unitId = this._playerManager.getNextUnitId();
                player1Commands.push(this.createSwapUnitCommand(player1Id, unitId, UnitType.archer, archer1Pos));
                // 标记位置为已占用
                this._globalOccupiedPositions.add(`${archer1Pos.x},${archer1Pos.y}`);
                player1ArcherCount++;
            } else {
                LOG.warn(`玩家1无法在第${i + 1}次尝试中找到有效位置生成弓箭手`);
            }

            // 为玩家2准备弓箭手位置
            const archer2Pos = this.getRandomPositionAroundBase(
                player2Base.position,
                TestBattleScript.BASE_SURROUNDING_DISTANCE,
                this._globalOccupiedPositions
            );
            if (archer2Pos) {
                // 获取下一个可用的单位ID
                const unitId = this._playerManager.getNextUnitId();
                player2Commands.push(this.createSwapUnitCommand(player2Id, unitId, UnitType.archer, archer2Pos));
                // 标记位置为已占用
                this._globalOccupiedPositions.add(`${archer2Pos.x},${archer2Pos.y}`);
                player2ArcherCount++;
            } else {
                LOG.warn(`玩家2无法在第${i + 1}次尝试中找到有效位置生成弓箭手`);
            }
        }

        LOG.log(
            `弓箭手生成完成 - 玩家1: ${player1ArcherCount}/${TestBattleScript.ARCHERS_PER_PLAYER}, 玩家2: ${player2ArcherCount}/${TestBattleScript.ARCHERS_PER_PLAYER}`
        );

        // 按回合执行命令序列
        this.executeCommandsByTurn(player1Commands, player2Commands, () => {
            LOG.log('弓箭手生成完成');
            if (callback) callback();
        });
    }

    /**
     * 获取基地周围的随机位置（带已占用位置检查）
     * @param basePosition 基地位置
     * @param distance 最大距离
     * @param occupiedPositions 已占用位置的集合
     * @returns 随机位置，如果找不到有效位置则返回undefined
     */
    private getRandomPositionAroundBase(
        basePosition: { x: number; y: number },
        distance: number,
        occupiedPositions: Set<string>
    ): { x: number; y: number } | undefined {
        // 首先尝试系统化搜索，确保覆盖所有可能的位置
        const validPositions: { x: number; y: number }[] = [];

        // 收集所有有效位置
        for (let offsetX = -distance; offsetX <= distance; offsetX++) {
            for (let offsetY = -distance; offsetY <= distance; offsetY++) {
                const newX = basePosition.x + offsetX;
                const newY = basePosition.y + offsetY;
                const positionKey = `${newX},${newY}`;

                // 检查位置是否有效
                if (this._mapManager.isValidPosition(newX, newY) && !occupiedPositions.has(positionKey)) {
                    const tile = this._mapManager.getTile(newX, newY);
                    // 确保位置是平地且没有实体
                    if (tile && tile.tileType === TildeType.flat && tile.entityId === undefined) {
                        validPositions.push({ x: newX, y: newY });
                    }
                }
            }
        }

        // 如果没有找到有效位置，记录详细信息并返回undefined
        if (validPositions.length === 0) {
            LOG.warn(
                `无法在基地 (${basePosition.x}, ${basePosition.y}) 周围距离 ${distance} 内找到有效位置。已占用位置数量: ${occupiedPositions.size}`
            );
            return undefined;
        }

        // 从有效位置中随机选择一个
        const randomIndex = Math.floor(Math.random() * validPositions.length);
        const selectedPosition = validPositions[randomIndex];

        LOG.log(
            `在基地 (${basePosition.x}, ${basePosition.y}) 周围找到 ${validPositions.length} 个有效位置，选择了 (${selectedPosition.x}, ${selectedPosition.y})`
        );
        return selectedPosition;
    }

    /**
     * 步骤3：开始战斗循环
     * @param player1Id 玩家1 ID
     * @param player2Id 玩家2 ID
     * @param rounds 回合数
     */
    private startBattleLoop(player1Id: string, player2Id: string, rounds: number) {
        LOG.log(`开始战斗循环，总回合数: ${rounds}`);

        let currentRound = 0;

        const battleInterval = setInterval(() => {
            // 检查是否达到回合上限
            if (currentRound >= rounds) {
                clearInterval(battleInterval);
                LOG.log('战斗循环结束');

                // 执行结束命令
                this.executeEndCommand(player1Id);
                LOG.log('已执行结束命令');

                // 如果启用了命令日志记录，则在所有命令执行完成后保存
                if (GameConfig.enableCmdLogging && this._commandLogs.length > 0) {
                    this._saveCommandLogs();
                }

                return;
            }

            currentRound++;
            // 增加轮次计数
            this._currentRound++;
            LOG.log(`执行轮次 ${this._currentRound}，战斗回合 ${currentRound}/${rounds}`);

            // 玩家1回合
            this.executePlayerTurn(player1Id, player2Id);

            // 玩家2回合
            this.executePlayerTurn(player2Id, player1Id);
        }, 100); // 每100毫秒执行一次
    }

    /**
     * 执行玩家回合
     * @param playerId 当前玩家ID
     * @param opponentId 对手玩家ID
     */
    private executePlayerTurn(playerId: string, opponentId: string) {
        // 获取玩家所有单位
        const units = this._playerManager.getPlayerAllUnits(playerId);

        // 为每个单位执行行动
        for (const unit of units) {
            let hasActed = false;

            // 获取单位当前位置的地图格子
            const tile = this._mapManager.getTile(unit.position.x, unit.position.y);
            if (!tile) continue;

            // 根据单位类型执行不同的行为
            if (unit.type === UnitType.doctor) {
                // 治疗兵：寻找友军进行治疗
                hasActed = this.tryHealFriendlyUnit(playerId, unit);
            } else if (unit.type === UnitType.soldier || unit.type === UnitType.archer) {
                // 士兵和弓箭手：寻找敌军进行攻击
                hasActed = this.tryAttackEnemyEntity(playerId, unit);
            } else if (unit.type === UnitType.worker) {
                // 工人：尝试建造城墙，每个建造兵只建造一座
                if (!this.workersWhoBuiltWall.has(unit.id)) {
                    const distanceToMidline = this.getDistanceToMidline(unit.position.x);
                    if (7 < distanceToMidline && distanceToMidline <= 10) {
                        // 尝试建造城墙
                        hasActed = this.tryBuildWall(playerId, unit);

                        // 如果成功建造了城墙，标记该建造兵已建造过城墙
                        if (hasActed) {
                            this.workersWhoBuiltWall.add(unit.id);
                        }
                    }
                } else if (!this.workersWhoBuiltTower.has(unit.id)) {
                    // 工人：尝试建造防御塔，每个建造兵只建造一座
                    const distanceToMidline = this.getDistanceToMidline(unit.position.x);
                    if (distanceToMidline <= 6) {
                        // 尝试建造防御塔
                        hasActed = this.tryBuildTower(playerId, unit);

                        // 如果成功建造了防御塔，标记该建造兵已建造过防御塔
                        if (hasActed) {
                            this.workersWhoBuiltTower.add(unit.id);
                        }
                    }
                }
            } else if (unit.type === UnitType.collect) {
                // 采集兵：尝试采集周围的资源，如果没有则移动到最近的资源点
                hasActed = this.tryCollectResource(playerId, unit);

                // 如果没有采集到资源，移动到最近的资源点
                if (!hasActed) {
                    hasActed = this.moveTowardsNearestResource(playerId, unit);
                }
            }

            // 如果没有执行任何行动，尝试随机移动
            if (!hasActed) {
                this.tryRandomMove(playerId, unit.id);
            }
        }

        // 获取玩家所有建筑
        const buildings = this._playerManager.getPlayerAllBuildings(playerId);

        // 为每个防御塔执行攻击行动
        for (const building of buildings) {
            if (building.type === BuildingType.tower) {
                // 防御塔：检查攻击范围内是否有敌方单位，有则攻击
                this.tryTowerAttackEnemyEntity(playerId, building);
            }
        }

        // 玩家回合结束，执行缓存的命令
        const playerCommands = this._playerCommandCache.get(playerId);
        if (playerCommands && playerCommands.length > 0) {
            LOG.log(`玩家 ${playerId} 回合结束，执行 ${playerCommands.length} 个缓存命令`);
            gc.battle.submitRoundCommands(playerId, playerCommands);
            // 清空该玩家的命令缓存
            this._playerCommandCache.set(playerId, []);
        }
    }

    /**
     * 防御塔尝试攻击敌方单位
     * @param playerId 玩家ID
     * @param tower 防御塔建筑
     * @returns 是否成功执行攻击
     */
    private tryTowerAttackEnemyEntity(playerId: string, tower: BuildingModel): boolean {
        // 获取防御塔的攻击范围
        const towerConfig = BuildingConfig[tower.type];
        const attackRange = towerConfig.attackRange;

        // 检查四个方向的攻击范围
        const directions = [
            { dx: 0, dy: -1 }, // 上
            { dx: 0, dy: 1 },  // 下
            { dx: -1, dy: 0 }, // 左
            { dx: 1, dy: 0 }   // 右
        ];

        for (const direction of directions) {
            for (let range = 1; range <= attackRange; range++) {
                // 计算目标位置
                const targetX = tower.position.x + direction.dx * range;
                const targetY = tower.position.y + direction.dy * range;

                // 检查目标位置是否有效
                if (!this._mapManager.isValidPosition(targetX, targetY)) {
                    break;
                }

                // 获取目标位置的地图格子
                const targetTile = this._mapManager.getTile(targetX, targetY);

                // 如果目标位置有其他地形（防御塔可以穿越河流攻击）
                if (targetTile && targetTile.tileType !== TildeType.flat && targetTile.tileType !== TildeType.river) {
                    break;
                }

                // 如果目标位置有阻隔物（单位、建筑）
                if (targetTile && targetTile.entityId !== undefined) {
                    // 如果是自己人，阻挡攻击
                    if (targetTile.playerId === playerId) {
                        break;
                    }
                    // 找到敌方单位，执行攻击
                    if (targetTile.entityType === EntityType.unit) {
                        // 计算偏移位置
                        const offsetPosition = {
                            x: direction.dx * range,
                            y: direction.dy * range
                        };
                        // 攻击敌方单位
                        this.executeCommand(this.createAttackCommand(
                            playerId,
                            tower.id,
                            EntityType.building,
                            tower.type,
                            targetTile.entityId,
                            EntityType.unit,
                            targetTile.unitType,
                            offsetPosition,
                            this._currentRound
                        ));
                        LOG.log(`玩家 ${playerId} 的防御塔 ${tower.id} 攻击了位置 (${targetX}, ${targetY}) 的敌方单位`);
                        return true;
                    } else if (targetTile.entityType === EntityType.building) {
                        // 计算偏移位置
                        const offsetPosition = {
                            x: direction.dx * range,
                            y: direction.dy * range
                        };
                        // 攻击敌方建筑
                        this.executeCommand(this.createAttackCommand(
                            playerId,
                            tower.id,
                            EntityType.building,
                            tower.type,
                            targetTile.entityId,
                            EntityType.building,
                            targetTile.buildingType,
                            offsetPosition,
                            this._currentRound
                        ));
                        LOG.log(`玩家 ${playerId} 的防御塔 ${tower.id} 攻击了位置 (${targetX}, ${targetY}) 的敌方建筑`);
                        return true;
                    }
                }
            }
        }

        return false;
    }

    /**
     * 尝试治疗友军单位
     * @param playerId 玩家ID
     * @param unit 治疗兵单位
     * @returns 是否成功执行治疗
     */
    private tryHealFriendlyUnit(playerId: string, unit: UnitModel): boolean {
        // 获取单位的治疗范围
        const unitConfig = UnitConfig[unit.type];
        const healRange = unitConfig ? unitConfig.attackRange : 1;

        // 检查四个方向的治疗范围
        const directions = [
            { dx: 0, dy: -1 }, // 上
            { dx: 0, dy: 1 },  // 下
            { dx: -1, dy: 0 }, // 左
            { dx: 1, dy: 0 }   // 右
        ];

        for (const direction of directions) {
            for (let range = 1; range <= healRange; range++) {
                // 计算目标位置
                const targetX = unit.position.x + direction.dx * range;
                const targetY = unit.position.y + direction.dy * range;

                // 检查目标位置是否有效
                if (!this._mapManager.isValidPosition(targetX, targetY)) {
                    break;
                }

                // 获取目标位置的地图格子
                const targetTile = this._mapManager.getTile(targetX, targetY);

                // 如果目标位置有其他地形（弓箭手可以穿越河流攻击）
                if (targetTile && targetTile.tileType !== TildeType.flat && targetTile.tileType !== TildeType.river) {
                    // 如果是弓箭手，可以穿越河流攻击
                    if (unit.type !== UnitType.archer) {
                        break;
                    }
                } else if (targetTile && targetTile.tileType === TildeType.river && unit.type !== UnitType.archer) {
                    // 非弓箭手不能穿越河流攻击
                    break;
                }

                // 如果目标位置有实体
                if (targetTile && targetTile.entityId !== undefined) {
                    // 如果是敌方单位或建筑，阻挡治疗
                    if (targetTile.playerId !== playerId) {
                        break;
                    }
                    // 找到友军单位，执行治疗
                    if (targetTile.entityType === EntityType.unit) {
                        // 检查目标是否为友军单位且需要治疗
                        const targetUnit = this._playerManager.getPlayerUnit(playerId, targetTile.entityId);
                        if (targetUnit) {
                            const maxHp = UnitConfig[targetUnit.type].hp;
                            if (targetUnit.hp < maxHp) {
                                // 计算偏移位置
                                const offsetPosition = {
                                    x: direction.dx * range,
                                    y: direction.dy * range
                                };
                                // 执行治疗命令
                                this.executeCommand(this.createHealCommand(
                                    playerId,
                                    unit.id,
                                    targetTile.entityId,
                                    targetTile.unitType as UnitType,
                                    offsetPosition,
                                    this._currentRound
                                ));
                                LOG.log(`玩家 ${playerId} 的治疗兵 ${unit.id} 治疗了位置 (${targetX}, ${targetY}) 的友军单位`);
                                return true;
                            }
                        }
                        break; // 找到友军单位但不需要治疗，阻挡继续搜索
                    } else {
                        break; // 友军建筑阻挡治疗
                    }
                }
            }
        }
        return false;
    }

    /**
     * 尝试攻击敌军单位
     * @param playerId 玩家ID
     * @param unit 士兵单位
     * @returns 是否成功执行攻击
     */
    private tryAttackEnemyEntity(playerId: string, unit: UnitModel): boolean {
        // 获取单位的攻击范围
        const unitConfig = UnitConfig[unit.type];
        const attackRange = unitConfig ? unitConfig.attackRange : 1;

        // 检查四个方向的攻击范围
        const directions = [
            { dx: 0, dy: -1 }, // 上
            { dx: 0, dy: 1 },  // 下
            { dx: -1, dy: 0 }, // 左
            { dx: 1, dy: 0 }   // 右
        ];

        for (const direction of directions) {
            for (let range = 1; range <= attackRange; range++) {
                // 计算目标位置
                const targetX = unit.position.x + direction.dx * range;
                const targetY = unit.position.y + direction.dy * range;

                // 检查目标位置是否有效
                if (!this._mapManager.isValidPosition(targetX, targetY)) {
                    break;
                }

                // 获取目标位置的地图格子
                const targetTile = this._mapManager.getTile(targetX, targetY);

                // 如果目标位置有其他地形（攻击范围大于1的单位可以穿越河流攻击）
                if (targetTile && targetTile.tileType !== TildeType.flat && targetTile.tileType !== TildeType.river) {
                    break;
                } else if (targetTile && targetTile.tileType === TildeType.river && attackRange === 1) {
                    // 攻击范围为1的单位不能穿越河流
                    break;
                }

                // 如果目标位置有阻隔物（建筑）
                if (targetTile && targetTile.entityId !== undefined) {
                    // 如果是自己人的建筑，阻挡攻击（单位不阻挡）
                    if (targetTile.playerId === playerId && targetTile.entityType === EntityType.building) {
                        continue;
                    }
                    // 找到敌方单位，执行攻击
                    if (targetTile.entityType === EntityType.unit) {
                        // 计算偏移位置
                        const offsetPosition = {
                            x: direction.dx * range,
                            y: direction.dy * range
                        };
                        // 攻击敌方单位
                        this.executeCommand(this.createAttackCommand(
                            playerId,
                            unit.id,
                            EntityType.unit,
                            unit.type,
                            targetTile.entityId,
                            EntityType.unit,
                            targetTile.unitType,
                            offsetPosition,
                            this._currentRound
                        ));
                        LOG.log(`玩家 ${playerId} 的单位 ${unit.id} 攻击了位置 (${targetX}, ${targetY}) 的敌方单位`);
                        return true;
                    } else if (targetTile.entityType === EntityType.building) {
                        // 计算偏移位置
                        const offsetPosition = {
                            x: direction.dx * range,
                            y: direction.dy * range
                        };
                        // 攻击敌方建筑
                        this.executeCommand(this.createAttackCommand(
                            playerId,
                            unit.id,
                            EntityType.unit,
                            unit.type,
                            targetTile.entityId,
                            EntityType.building,
                            targetTile.buildingType,
                            offsetPosition,
                            this._currentRound
                        ));
                        LOG.log(`玩家 ${playerId} 的单位 ${unit.id} 攻击了位置 (${targetX}, ${targetY}) 的敌方建筑`);
                        return true;
                    }
                }
            }
        }
        return false;
    }

    /**
     * 尝试建造防御塔
     * @param playerId 玩家ID
     * @param unit 建造兵单位
     * @returns 是否成功执行建造
     */
    private tryBuildTower(playerId: string, unit: UnitModel): boolean {
        // 检查周围四个方向，寻找可建造的位置
        const directions = [DirectionType.UP, DirectionType.RIGHT, DirectionType.DOWN, DirectionType.LEFT];

        for (const direction of directions) {
            // 获取目标位置
            const [targetX, targetY] = this._mapManager.getPositionInDirection(unit.position.x, unit.position.y, direction);

            // 检查目标位置是否有效且可建造
            if (this._mapManager.isValidPosition(targetX, targetY)) {
                const targetTile = this._mapManager.getTile(targetX, targetY);

                // 检查目标位置是否为平地且没有其他实体
                if (targetTile && targetTile.tileType === TildeType.flat && targetTile.entityId === undefined) {
                    // 获取下一个建筑ID
                    const towerId = this._playerManager.getNextBuildingId();
                    // 执行建造命令
                    this.executeCommand(
                        this.createBuildCommand(
                            playerId,
                            unit.id,
                            towerId,
                            BuildingType.tower,
                            { x: targetX, y: targetY },
                            this._currentRound
                        )
                    );
                    // 标记位置为已占用
                    this._globalOccupiedPositions.add(`${targetX},${targetY}`);
                    LOG.log(`玩家 ${playerId} 的工人 ${unit.id} 在位置 (${targetX}, ${targetY}) 建造了防御塔`);
                    return true;
                }
            }
        }

        return false;
    }

    /**
     * 计算到地图中线的距离
     * @param x 当前X坐标
     * @returns 到中线的距离
     */
    private getDistanceToMidline(x: number): number {
        // 地图是50x50，中线在x=25
        const midline = 25;
        return Math.abs(x - midline);
    }

    /**
     * 尝试建造城墙
     * @param playerId 玩家ID
     * @param unit 建造兵单位
     * @returns 是否成功建造城墙
     */
    private tryBuildWall(playerId: string, unit: UnitModel): boolean {
        // 检查周围四个方向，寻找可建造的位置
        const directions = [DirectionType.UP, DirectionType.RIGHT, DirectionType.DOWN, DirectionType.LEFT];

        for (const direction of directions) {
            // 获取目标位置
            const [targetX, targetY] = this._mapManager.getPositionInDirection(unit.position.x, unit.position.y, direction);

            // 检查目标位置是否有效且可建造
            if (this._mapManager.isValidPosition(targetX, targetY)) {
                const targetTile = this._mapManager.getTile(targetX, targetY);

                // 检查目标位置是否为平地且没有其他实体
                if (targetTile && targetTile.tileType === TildeType.flat && targetTile.entityId === undefined) {
                    // 获取下一个建筑ID
                    const wallId = this._playerManager.getNextBuildingId();
                    // 执行建造命令
                    this.executeCommand(
                        this.createBuildCommand(
                            playerId,
                            unit.id,
                            wallId,
                            BuildingType.wall,
                            { x: targetX, y: targetY },
                            this._currentRound
                        )
                    );
                    // 标记位置为已占用
                    this._globalOccupiedPositions.add(`${targetX},${targetY}`);
                    LOG.log(`玩家 ${playerId} 的工人 ${unit.id} 在位置 (${targetX}, ${targetY}) 建造了城墙`);
                    return true;
                }
            }
        }

        return false;
    }

    /**
     * 尝试采集资源
     * @param playerId 玩家ID
     * @param unit 采集兵单位
     * @param tile 目标地块（如果提供）
     * @param direction 采集方向（如果提供）
     * @returns 是否成功执行采集
     */
    private tryCollectResource(playerId: string, unit: UnitModel, tile?: MapTile, direction?: DirectionType): boolean {
        // 如果没有提供目标地块和方向，则检查四个方向是否有资源
        if (!tile || direction === undefined) {
            // 检查四个方向
            for (const dir of [DirectionType.UP, DirectionType.RIGHT, DirectionType.DOWN, DirectionType.LEFT]) {
                const [targetX, targetY] = this._mapManager.getPositionInDirection(unit.position.x, unit.position.y, dir);

                // 检查目标位置是否有效
                if (this._mapManager.isValidPosition(targetX, targetY)) {
                    const targetTile = this._mapManager.getTile(targetX, targetY);

                    // 如果目标位置是资源地形，执行采集
                    if (targetTile && isResourceTildeType(targetTile.tileType)) {
                        return this.tryCollectResource(playerId, unit, targetTile, dir);
                    }
                }
            }
            return false;
        }

        // 计算偏移位置
        const offsetPosition = {
            x: tile.x - unit.position.x,
            y: tile.y - unit.position.y
        };
        // 创建采集命令
        this.executeCommand(this.createCollectCommand(
            playerId,
            unit.id,
            tile.tileType,
            offsetPosition,
            direction,
            this._currentRound
        ));
        LOG.log(`玩家 ${playerId} 的采集兵 ${unit.id} 在位置 (${unit.position.x}, ${unit.position.y}) 向 ${DirectionType[direction]} 方向采集了 ${TildeType[tile.tileType]} 资源`);
        return true;
    }

    /**
     * 创建采集命令
     * @param playerId 玩家ID
     * @param unitId 采集兵ID
     * @param resourceType 资源类型
     * @param targetPosition 目标资源位置
     * @param direction 采集方向
     * @param round 回合数
     * @returns 采集命令
     */
    private createCollectCommand(
        playerId: string,
        unitId: number,
        resourceType: TildeType,
        offsetPosition: { x: number; y: number },
        direction: DirectionType,
        round?: number
    ): CommandParam<keyof CommandParamMap> {

        // 创建采集命令
        return {
            player: playerId,
            type: CommandType.collect, // 使用collect命令类型
            round: round || this._currentRound, // 使用传入的轮次或当前轮次
            param: {
                self: {
                    type: EntityType.unit,
                    utype: UnitType.collect,
                    id: unitId,
                },
                target: {
                    type: EntityType.terrain,
                    utype: resourceType,
                    id: 0, // 地形没有特定ID
                },
                offsetPosition: offsetPosition,
            },
        };
    }

    /**
     * 移动到最近的资源点
     * @param playerId 玩家ID
     * @param unit 采集兵单位
     * @returns 是否成功执行移动
     */
    private moveTowardsNearestResource(playerId: string, unit: UnitModel): boolean {
        // 寻找最近的资源点
        const resourceTiles: { tile: MapTile; distance: number }[] = [];

        // 遍历地图寻找资源地形
        const mapData = this._mapManager.getMapData();
        if (!mapData) return false;

        for (let y = 0; y < mapData.length; y++) {
            for (let x = 0; x < mapData[y].length; x++) {
                const tile = mapData[y][x];
                if (isResourceTildeType(tile.tileType)) {
                    // 计算与采集兵的距离
                    const distance = Math.abs(tile.x - unit.position.x) + Math.abs(tile.y - unit.position.y);
                    resourceTiles.push({ tile, distance });
                }
            }
        }

        // 按距离排序
        resourceTiles.sort((a, b) => a.distance - b.distance);

        // 如果找到资源点，向其移动
        if (resourceTiles.length > 0) {
            const nearestResource = resourceTiles[0].tile;

            // 确定移动方向
            let moveDirection: DirectionType | null = null;

            // 优先选择x方向移动
            if (
                nearestResource.x > unit.position.x &&
                this._mapManager.canUnitMoveToDirection(unit.id, playerId, DirectionType.RIGHT)
            ) {
                moveDirection = DirectionType.RIGHT;
            } else if (
                nearestResource.x < unit.position.x &&
                this._mapManager.canUnitMoveToDirection(unit.id, playerId, DirectionType.LEFT)
            ) {
                moveDirection = DirectionType.LEFT;
            }
            // 如果x方向不能移动，尝试y方向
            else if (
                nearestResource.y > unit.position.y &&
                this._mapManager.canUnitMoveToDirection(unit.id, playerId, DirectionType.DOWN)
            ) {
                moveDirection = DirectionType.DOWN;
            } else if (
                nearestResource.y < unit.position.y &&
                this._mapManager.canUnitMoveToDirection(unit.id, playerId, DirectionType.UP)
            ) {
                moveDirection = DirectionType.UP;
            }

            // 如果找到可移动方向，执行移动
            if (moveDirection !== null) {
                const [targetX, targetY] = this._mapManager.getPositionInDirection(
                    unit.position.x,
                    unit.position.y,
                    moveDirection
                );
                this.executeCommand(this.createMoveCommand(playerId, unit.id, { x: targetX, y: targetY }, this._currentRound));
                LOG.log(
                    `玩家 ${playerId} 的采集兵 ${unit.id} 从 (${unit.position.x}, ${unit.position.y}) 移动到 (${targetX}, ${targetY})，朝向资源点 (${nearestResource.x}, ${nearestResource.y})`
                );
                return true;
            }
        }

        return false;
    }

    /**
     * 尝试随机移动单位
     * @param playerId 玩家ID
     * @param unitId 单位ID
     */
    private tryRandomMove(playerId: string, unitId: number) {
        // 获取单位
        const unit = this._playerManager.getPlayerUnit(playerId, unitId);
        if (!unit) return;

        // 获取可移动的方向列表
        const availableDirections: DirectionType[] = [];

        // 检查单位是否可以向各个方向移动
        if (this._mapManager.canUnitMoveToDirection(unitId, playerId, DirectionType.UP)) {
            availableDirections.push(DirectionType.UP);
        }
        if (this._mapManager.canUnitMoveToDirection(unitId, playerId, DirectionType.RIGHT)) {
            availableDirections.push(DirectionType.RIGHT);
        }
        if (this._mapManager.canUnitMoveToDirection(unitId, playerId, DirectionType.DOWN)) {
            availableDirections.push(DirectionType.DOWN);
        }
        if (this._mapManager.canUnitMoveToDirection(unitId, playerId, DirectionType.LEFT)) {
            availableDirections.push(DirectionType.LEFT);
        }

        // 如果没有可移动的方向，直接返回
        if (availableDirections.length === 0) return;

        // 选择移动方向
        let selectedDirection: DirectionType;

        // 判断是否已经越过地图中线
        const crossedMiddle =
            (this._playerManager.isLeftSidePlayer(playerId) && unit.position.x >= 25) ||
            (this._playerManager.isRightSidePlayer(playerId) && unit.position.x <= 24);

        if (!crossedMiddle) {
            // 没有越过中线时，左侧玩家优先往右走，右侧玩家优先往左移动
            if (this._playerManager.isLeftSidePlayer(playerId)) {
                // 左侧玩家优先往右走
                if (availableDirections.indexOf(DirectionType.RIGHT) !== -1) {
                    selectedDirection = DirectionType.RIGHT;
                } else {
                    // 如果不能往右走，随机选择其他方向
                    const otherDirections = availableDirections.filter((dir) => dir !== DirectionType.RIGHT);
                    selectedDirection = otherDirections[Math.floor(Math.random() * otherDirections.length)];
                }
            } else {
                // 右侧玩家
                // 右侧玩家优先往左走
                if (availableDirections.indexOf(DirectionType.LEFT) !== -1) {
                    selectedDirection = DirectionType.LEFT;
                } else {
                    // 如果不能往左走，随机选择其他方向
                    const otherDirections = availableDirections.filter((dir) => dir !== DirectionType.LEFT);
                    selectedDirection = otherDirections[Math.floor(Math.random() * otherDirections.length)];
                }
            }
        } else {
            // 已经越过中线，随机选择方向
            selectedDirection = availableDirections[Math.floor(Math.random() * availableDirections.length)];
        }

        // 获取目标位置
        const [targetX, targetY] = this._mapManager.getPositionInDirection(unit.position.x, unit.position.y, selectedDirection);

        // 执行移动命令
        this.executeCommand(this.createMoveCommand(playerId, unitId, { x: targetX, y: targetY }, this._currentRound));
    }

    /**
     * 执行单个命令
     * @param command 要执行的命令
     */
    private executeCommand(command: CommandParam<keyof CommandParamMap>) {
        try {
            // 在执行移动命令前，记录原位置以便更新全局占用位置集合
            let oldPosition: { x: number; y: number } | null = null;
            if (command.type === CommandType.move && command.param) {
                const moveParam = command.param as any;
                if (moveParam.unitId) {
                    const unit = this._playerManager.getPlayerUnit(command.player, moveParam.unitId);
                    if (unit) {
                        oldPosition = { x: unit.position.x, y: unit.position.y };
                    }
                }
            }

            // 执行命令

            // 方式1: 直接渲染
            // this._battleSceneInstance.handleBattleCommand(command.type, command);

            // 方式2: 走battle
            if (command.type === CommandType.init) {
                // init命令立即执行
                gc.battle.cmd(command);
            } else {
                // 其他命令缓存起来，等待回合结束后统一执行
                if (!this._playerCommandCache.has(command.player)) {
                    this._playerCommandCache.set(command.player, []);
                }
                this._playerCommandCache.get(command.player)!.push(command);
            }

            // 同步命令到PlayerManager（包含地图更新）
            this._playerManager.handleCommand(command);

            // 处理移动命令后的全局占用位置集合更新
            if (command.type === CommandType.move && command.param && oldPosition) {
                const moveParam = command.param as any;
                if (moveParam.position) {
                    // 从旧位置移除
                    this._globalOccupiedPositions.delete(`${oldPosition.x},${oldPosition.y}`);
                    // 添加到新位置
                    this._globalOccupiedPositions.add(`${moveParam.position.x},${moveParam.position.y}`);
                }
            }

            // 处理攻击命令可能导致的单位死亡，需要从全局占用位置集合中移除
            if (command.type === CommandType.attack && command.param) {
                const attackParam = command.param as any;
                if (attackParam.target && attackParam.target.type === EntityType.unit) {
                    // 检查目标单位是否已死亡（血量为0或负数）
                    const targetUnit = this._playerManager.getPlayerUnit(attackParam.target.player, attackParam.target.id);
                    if (!targetUnit || targetUnit.hp <= 0) {
                        // 单位已死亡，从全局占用位置集合中移除
                        if (attackParam.target.position) {
                            this._globalOccupiedPositions.delete(
                                `${attackParam.target.position.x},${attackParam.target.position.y}`
                            );
                        }
                    }

                    // 处理士兵溅射击杀的单位，需要从全局占用位置集合中移除
                    if (attackParam.attacker && attackParam.attacker.type === EntityType.unit) {
                        const attackerUnit = this._playerManager.getPlayerUnit(attackParam.attacker.player, attackParam.attacker.id);
                        if (attackerUnit && attackerUnit.type === UnitType.soldier && attackParam.target.position && attackParam.offsetPosition) {
                            // 计算溅射位置（参考PlayerManager中的calculateSplashPositions逻辑）
                            const targetPos = attackParam.target.position;
                            const offset = attackParam.offsetPosition;
                            const splashPositions: { x: number; y: number }[] = [];

                            // 判断攻击方向：水平攻击还是垂直攻击
                            if (Math.abs(offset.x) > Math.abs(offset.y)) {
                                // 水平攻击，溅射到上下位置
                                splashPositions.push({ x: targetPos.x, y: targetPos.y - 1 });
                                splashPositions.push({ x: targetPos.x, y: targetPos.y + 1 });
                            } else {
                                // 垂直攻击，溅射到左右位置
                                splashPositions.push({ x: targetPos.x - 1, y: targetPos.y });
                                splashPositions.push({ x: targetPos.x + 1, y: targetPos.y });
                            }

                            // 检查溅射位置的单位是否被击杀
                            for (const splashPos of splashPositions) {
                                // 检查该位置是否在地图范围内
                                if (splashPos.x >= 0 && splashPos.x < this._mapManager.mapWidth &&
                                    splashPos.y >= 0 && splashPos.y < this._mapManager.mapHeight) {

                                    const splashTile = this._mapManager.getTile(splashPos.x, splashPos.y);
                                    if (splashTile && splashTile.entityType === EntityType.unit &&
                                        splashTile.playerId !== attackParam.attacker.player) {

                                        // 检查该位置的单位是否已被溅射击杀
                                        const splashUnit = this._playerManager.getPlayerUnit(splashTile.playerId, splashTile.entityId);
                                        if (!splashUnit || splashUnit.hp <= 0) {
                                            // 溅射击杀的单位，从全局占用位置集合中移除
                                            this._globalOccupiedPositions.delete(`${splashPos.x},${splashPos.y}`);
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }

            // 如果启用了命令日志记录，则记录命令
            if (GameConfig.enableCmdLogging) {
                // 记录命令到日志数组
                this._commandLogs.push(command);
            }

            LOG.log(`已执行命令 - 类型: ${command.type}, 玩家: ${command.player}`);
        } catch (error) {
            LOG.error(`执行命令异常 - 类型: ${command.type}:`, error);
        }
    }

    /**
     * 按回合执行命令序列（不使用setTimeout）
     * @param player1Commands 玩家1的命令数组
     * @param player2Commands 玩家2的命令数组
     * @param callback 命令执行完成后的回调函数
     */
    private executeCommandsByTurn(
        player1Commands: CommandParam<keyof CommandParamMap>[],
        player2Commands: CommandParam<keyof CommandParamMap>[],
        callback?: () => void
    ) {
        // 检查命令是否为空
        if ((!player1Commands || player1Commands.length === 0) && (!player2Commands || player2Commands.length === 0)) {
            LOG.log('没有命令需要执行');
            if (callback) callback();
            return;
        }

        // 获取最大回合数
        const maxTurns = Math.max(player1Commands.length, player2Commands.length);

        for (let currentTurn = 0; currentTurn < maxTurns; currentTurn++) {
            // 增加轮次计数
            this._currentRound++;
            LOG.log(`开始执行轮次 ${this._currentRound}`);

            // 执行玩家1的命令（如果有）
            if (currentTurn < player1Commands.length && player1Commands[currentTurn]) {
                player1Commands[currentTurn].round = this._currentRound;
                this.executeCommand(player1Commands[currentTurn]);
                LOG.log(`轮次 ${this._currentRound}: 玩家1执行命令`);
            }

            // 执行玩家2的命令（如果有）
            if (currentTurn < player2Commands.length && player2Commands[currentTurn]) {
                player2Commands[currentTurn].round = this._currentRound;
                this.executeCommand(player2Commands[currentTurn]);
                LOG.log(`轮次 ${this._currentRound}: 玩家2执行命令`);
            }

            // 回合结束，分别执行两个玩家的缓存命令
            for (const [playerId, commands] of this._playerCommandCache) {
                if (commands && commands.length > 0) {
                    LOG.log(`轮次 ${this._currentRound} 结束，玩家 ${playerId} 执行 ${commands.length} 个缓存命令`);
                    gc.battle.submitRoundCommands(playerId, commands);
                    // 清空该玩家的命令缓存
                    this._playerCommandCache.set(playerId, []);
                }
            }
        }

        // 所有命令执行完成，调用回调函数
        if (callback) callback();
    }

    /**
     * 执行结束命令
     */
    private executeEndCommand(playerId: string) {
        const endCommand = this.createEndCommand(playerId);
        this.executeCommand(endCommand);
    }

    /**
     * 创建初始化命令数据
     */
    private createInitCommand(playerId1: string, playerId2: string): CommandParam<keyof CommandParamMap> {
        // 创建地图命令
        const initCommand: CommandParam<keyof CommandParamMap> = {
            player: playerId1,
            type: CommandType.init,
            round: this._currentRound,
            param: {
                map: 'main3',
                players: [playerId1, playerId2],
            },
        };
        return initCommand;
    }

    /**
     * 创建建造建筑命令
     */
    private createBuildCommand(
        playerId: string,
        unitId: number,
        buildingId: number,
        buildingType: BuildingType,
        position: { x: number; y: number },
        round?: number
    ): CommandParam<keyof CommandParamMap> {
        // 获取建造者单位
        const builder = this._playerManager.getPlayerUnit(playerId, unitId);

        // 计算相对于建造者的偏移位置
        const offsetPosition = {
            x: position.x - (builder ? builder.position.x : 0),
            y: position.y - (builder ? builder.position.y : 0),
        };

        // 创建建造命令
        return {
            player: playerId,
            type: CommandType.build, // 使用build命令类型
            round: round || this._currentRound, // 使用传入的轮次或当前轮次
            param: {
                self: {
                    type: EntityType.unit,
                    utype: UnitType.worker,
                    id: unitId,
                },
                target: {
                    type: EntityType.building,
                    utype: buildingType,
                    id: buildingId,
                },
                offsetPosition: offsetPosition,
            },
        };
    }

    /**
     * 创建并返回单位命令
     */
    private createSwapUnitCommand(
        playerId: string,
        unitId: number,
        utype: UnitType,
        position: { x: number; y: number },
        round?: number
    ): CommandParam<keyof CommandParamMap> {
        // 获取玩家的基地建筑
        const base = this._playerManager.getPlayerBuildingByType(playerId, BuildingType.base);

        // 计算相对于基地的偏移位置
        const offsetPosition = {
            x: position.x - base.position.x,
            y: position.y - base.position.y,
        };

        // 创建单位命令
        const soldierCommand: CommandParam<keyof CommandParamMap> = {
            player: playerId,
            type: CommandType.swap, // 使用swap命令类型来生产单位
            round: round || this._currentRound, // 使用传入的轮次或当前轮次
            param: {
                self: {
                    type: EntityType.building,
                    utype: BuildingType.base,
                    id: base.id,
                },
                target: {
                    type: EntityType.unit,
                    utype: utype,
                    id: unitId,
                },
                offsetPosition: offsetPosition,
            },
        };

        return soldierCommand;
    }

    /**
     * 创建单位移动命令
     */
    private createMoveCommand(
        playerId: string,
        unitId: number,
        position: { x: number; y: number },
        round?: number
    ): CommandParam<keyof CommandParamMap> {
        // 创建移动命令
        // 获取单位类型
        const unit = this._playerManager.getPlayerUnit(playerId, unitId);
        const unitType = unit ? unit.type : UnitType.soldier; // 默认为士兵类型

        // 计算相对于单位的偏移位置
        const offsetPosition = {
            x: position.x - (unit ? unit.position.x : 0),
            y: position.y - (unit ? unit.position.y : 0),
        };

        return {
            player: playerId,
            type: CommandType.move, // 使用move命令类型
            round: round || this._currentRound, // 使用传入的轮次或当前轮次
            param: {
                self: {
                    type: EntityType.unit,
                    utype: unitType,
                    id: unitId,
                },
                offsetPosition: offsetPosition,
            },
        };
    }

    /**
     * 创建攻击命令
     */
    private createAttackCommand(
        playerId: string,
        unitId: number,
        type: EntityType.unit | EntityType.building,
        utype: UnitType | BuildingType,
        targetId: number,
        targetType: EntityType.unit | EntityType.building,
        targetUtype: UnitType | BuildingType,
        offsetPosition: { x: number; y: number },
        round?: number
    ): CommandParam<keyof CommandParamMap> {

        // 创建攻击命令
        return {
            player: playerId,
            type: CommandType.attack, // 使用attack命令类型
            round: round || this._currentRound, // 使用传入的轮次或当前轮次
            param: {
                self: {
                    type: type,
                    utype: utype,
                    id: unitId,
                },
                target: {
                    type: targetType,
                    utype: targetUtype,
                    id: targetId,
                },
                offsetPosition: offsetPosition,
            },
        };
    }

    /**
     * 创建治疗命令
     */
    private createHealCommand(
        playerId: string,
        healerId: number,
        targetId: number,
        targetUtype: UnitType,
        offsetPosition: { x: number; y: number },
        round?: number
    ): CommandParam<keyof CommandParamMap> {

        // 创建治疗命令
        return {
            player: playerId,
            type: CommandType.heal, // 使用heal命令类型
            round: round || this._currentRound, // 使用传入的轮次或当前轮次
            param: {
                self: {
                    type: EntityType.unit,
                    utype: UnitType.doctor,
                    id: healerId,
                },
                target: {
                    type: EntityType.unit,
                    utype: targetUtype,
                    id: targetId,
                },
                offsetPosition: offsetPosition,
            },
        };
    }

    /**
     * 创建结束命令
     */
    private createEndCommand(playerId: string, round?: number): CommandParam<keyof CommandParamMap> {
        // 创建结束命令
        const otherPlayer = playerId === 'player1' ? 'player2' : 'player1';
        return {
            player: 'system',
            type: CommandType.end, // 使用end命令类型
            round: round || this._currentRound, // 使用传入的轮次或当前轮次
            param: {
                result: {
                    winner: playerId,
                    loser: otherPlayer,
                    msg: `达到${round || this._currentRound}回合，双方基地血量一致，玩家${playerId}击杀数更多(13 vs 8)，获胜！`,
                    playerStats: {
                        "player1": {
                            player: "player1",
                            rmb: 0,
                            baseHealth: 100,
                            kills: 13,
                            deaths: 8,
                            totalDamageDealt: 1530,
                            totalDamageReceived: 1360,
                            totalHealing: 0,
                            commandFailCount: 0
                        },
                        "player2": {
                            player: "player2",
                            rmb: 0,
                            baseHealth: 100,
                            kills: 8,
                            deaths: 13,
                            totalDamageDealt: 1360,
                            totalDamageReceived: 1530,
                            totalHealing: 0,
                            commandFailCount: 0
                        }
                    },
                    failedCommands: {}
                }
            }
        };
    }

    /**
     * 保存命令日志到文件
     */
    private _saveCommandLogs() {
        try {
            // 将命令日志数组转换为JSON字符串，每条命令一行
            const logContent = this._commandLogs.map((log) => JSON.stringify(log)).join('\n');

            // 创建Blob对象
            const blob = new Blob([logContent], { type: 'application/json' });
            // 创建下载链接
            const url = URL.createObjectURL(blob);
            // 创建a标签并设置属性
            const a = document.createElement('a');
            a.href = url;
            a.download = 'TestCmds.json';
            // 添加到文档中并触发点击
            document.body.appendChild(a);
            a.click();
            // 清理
            document.body.removeChild(a);
            URL.revokeObjectURL(url);

            LOG.log(`命令日志已保存到: TestCmds.json，共${this._commandLogs.length}条命令`);
        } catch (error) {
            LOG.error('保存命令日志失败:', error);
        }
    }
}
